import java.util.Scanner;
import java.util.Random;

public class gameD{
	static String bruh = "Bruh";
	public static boolean newLayer = false;
	public static void main(String[] args){
		//System.out.println(bruh);
		//InitializeEnv();
		System.out.println("Please enter your name: ");
		Scanner sc = new Scanner(System.in);
		String pName = sc.nextLine();
		Gamer player1 = new Gamer(pName,5,2,0);
		//Some Testings
		//Player m1 = new Player("Monster1",40,0,0);
		//player1.Attack(m1);
		//Main Process
		GameProcess(player1);

		System.out.println("The Game Ends");
	}
	static void InitializeEnv(){
		//System.out.println(bruh);
	}
	static void GameProcess(Gamer player){
		//Contains entering new layer,Initializeing components
		//Battle and calculating results
		int processLength = 5;
labelx:{
		   //---------------------------------------x
		   for(int i = 0;i<processLength;i++){
			   //Main Process
			   System.out.println("\033[2JWelcome to stage : " + i);
			   newLayer = true;
			   String mName = "Monster" + Integer.toString(i);
			   Player ms = new Player(mName,2*i-1,2*i,0);
			   	if(!player.CheckDeath()){
					break labelx;
				}
			   player.ChangeHealth(i);
		       player.printStats();
			   ms.printStats();
			   player.NormalUpgrade();

			   while(ms.CheckDeath()){
				   System.out.println("");
				   System.out.println("\033[42m------Player Attacks------\033[0m");
				   player.Attack(ms);
				   System.out.println("\033[46m \033[0m" + player.name + " now has "+ player.GetHealth() + " points of health");
				   System.out.println("");
				   if(!player.CheckDeath()){
					   break labelx;
				   }
			   }
		   }
		   //----------------------------------------x
}
	}
}

class Player{
	//Player has ability,luck and health,dies if health is down 2 zero
	int health;
	int ability;
	int luck;
	String name="";


	Player(String Enteredname,int h,int a, int l){
		health = h;
		ability = a;
		luck = l;
		name = Enteredname;
	}

	public int GetHealth(){
		return health;
	}
	public int GetAbility(){
		return ability;
	}
	public int GetLuck(){
		return luck;
	}
	public String GetName(){
		return name;
	}

	public boolean CheckDeath(){
		String state = health>0?"Alive":"DEAD";
		System.out.println("\033[41m \033[0m" + name + " is " + state);
		return health>0? true:false;
	}
	public void ChangeAbility(int dif){
		ability += dif;
		System.out.println("\033[47m \033[0m" + name + " now has " + ability + " points of ability");
	}
	public void ChangeLuck(int dif){
		luck += dif;
		System.out.println("\033[47m \033[0m" + name + " now has " + luck + " points of luck");
	}
	public void ChangeHealth(int dif){
		health += dif;
		System.out.println("\033[47m \033[0m" + name + " now has " + health + " points of health");
	}

	public void SpecialUpgrade(){

	}

	public void printStats(){
		System.out.println(name + " now has stats of : ");
		System.out.println("Health : "+health);
		System.out.println("Ability : "+ability);
		System.out.println("Luck : "+luck);
		System.out.println("");
	}

	public void Attack(Player target){
		printStats();
		target.printStats();
		int AbDifference = ability - target.GetAbility();
	    Random rd = new Random();
		float random = rd.nextFloat();
		if(random > 0.1f*(float)luck){
		//Normal
		ChangeHealth(-target.GetAbility());
		}
		else{
		//Lucky
		System.out.println("\033[42m"+ name + " is Very lucky that he doged the damage\033[0m");
		}
		target.ChangeHealth(-ability);
		
		String winner = AbDifference > 0 ? name : target.GetName();
		if(AbDifference > 0){
			//The attacker wins
			System.out.println("\033[46m \033[0m"+ name + " is attacking " + target.GetName() + " with a result of " + winner + " winning");
			System.out.println("\033[41m \033[0m" + target.GetName() + " loses " + Integer.toString(AbDifference) + " health");
			System.out.println("");
			target.ChangeHealth(-AbDifference);
		}
		else{
			//The attacker did not win

			if(AbDifference < 0){
				//The attacker loses
				System.out.println("\033[46m \033[0m"+ name + " is attacking " + target.GetName() + " with a result of " + winner + " winning");
				System.out.println("\033[41m \033[0m" + name + " will lose " + Integer.toString(-AbDifference) + " health");
				System.out.println("");
				if(gameD.newLayer){
					//Skill activate
					SpecialUpgrade();
					gameD.newLayer = false;
					return;
				}
				ChangeHealth(AbDifference);
			}
			else if (AbDifference == 0){
				//Nobody won
				System.out.println("Nobody won, so the monster loses 1 health");
				System.out.println("");
				if(gameD.newLayer){
					//Skill activate
					SpecialUpgrade();
					gameD.newLayer = false;
					return;
				}
				target.ChangeHealth(-1);
			}

		}
		//CheckDeath();
		//target.CheckDeath();
	}

}
class Gamer extends Player{

	public void SpecialUpgrade(){
		System.out.println("");
		System.out.println("\033[41m------Player is trying to activate a special skill------\033[0m");
		System.out.println("    You Didn't Win the Latest Fight    ");
		System.out.println("    You Can Now Perform An Upgrade (ONCE per new stage)");
		System.out.println("  Enter (a) to +2 Ability | (h) to +4 Health | (l) to +1 Luck | Other Entry's Will SKIP the Process");
		Scanner up = new Scanner(System.in);
		String choice;
		choice = up.nextLine();
		switch(choice){
			case "a":
				System.out.println("Upgraded Ability");
				ChangeAbility(2);
				break;
			case "h":
				System.out.println("Upgraded Health");
				ChangeHealth(4);
				break;
			case "l":
				System.out.println("Upgraded Luck");
				ChangeLuck(1);
				break;
			default:
				System.out.println("Your input is not recognized");
		}
	}
	public void NormalUpgrade(){
		System.out.println("");
		System.out.println("\033[41m------You can upgrade a stat entering a new stage ------\033[0m");
		System.out.println("    You Can Now Perform An Upgrade (ONCE per new stage)");
		System.out.println("  Enter (a) to +1 Ability | (h) to +2 Health | (l) to +1 Luck | Other Entry's Will SKIP the Process");
		Scanner up = new Scanner(System.in);
		String choice;
		choice = up.nextLine();
		switch(choice){
			case "a":
				System.out.println("Upgraded Ability");
				ChangeAbility(1);
				break;
			case "h":
				System.out.println("Upgraded Health");
				ChangeHealth(2);
				break;
			case "l":
				System.out.println("Upgraded Luck");
				ChangeLuck(1);
				break;
			default:
				System.out.println("Your input is not recognized");
		}
	}

	Gamer(String Enteredname,int h,int a, int l){
		super(Enteredname,h,a,l);
	}
}
